import matplotlib.pyplot as plt
import time

import datetime as dt
import easyquotation


import json,requests,datetime;    


import pandas as pd  #
import random

import numpy as np



class FlowPoint:
    left = 0
    right = 0
    x = 0
    y = 0
    def __init__(self, x , y , left, right):
        self.left = left
        self.right = right
        self.x = x
        self.y = y
    


class FlowManager:
    def __init__(self):
        self.x = 20
        self.step = 20
        self.size = 3
        self.update = 1
        self.count = 0
        self.time = dt.datetime.now()

    def foward(self):
        self.x = self.x + self.step
        self.update = 0
        self.count = 0
    def inc(self):
        self.count = self.count + 1
    def valid_time(self, time):
        diff = time - self.time
        diff_test = int((self.time - time).seconds/60)
        diff_min = int( diff.seconds/60);
        if self.update == 1 or  diff_min >= 1:
            if self.count < 10:
                self.update = 1
            else:
                self.foward()

            return True
        else:
            return False


class FlowBook:
    def __init__(self):
        self.lastPx = 0
        self.ask = 0
        self.bid = 0
        self.ask_vol = 0
        self.bid_vol = 0
        self.trade_vol = 0
        self.price_up = 0
        self.price_down = 0

class Market:
    def _init__(self):
        self.lastPx = 0
        self.ask1 = 0
        self.bid1 = 0
        self.ask_vol1 = 0
        self.bid_vol1 = 0
        self.trade_vol = 0
        self.open_price = 0
        self.time = dt.datetime.now()


order_flow_dict = {}

plt.ion()
class DynamicUpdate():
    #Suppose we know the x range
    min_x = 100
    max_x = 100
    i = 0
    xdata = []
    ydata = []
    def __init__(self): # this must  be __init__ , so lines can be member variable
        #Set up plot
        self.figure, self.ax = plt.subplots()
        self.lines, = self.ax.plot([],[], ' ')
        #Autoscale on unknown axis and known lims on the other
        #self.ax.set_autoscaley_on(True)
        self.ax.set_xlim(100)
        self.ax.set_ylim(80)
        #Other stuff
        #self.ax.grid()
        self.ax.invert_xaxis()
        self.ax.invert_yaxis()        
        ...

    def on_running(self, xdata, ydata, i, val,color):
        #Update data (with the new _and_ the old points)
        self.lines.set_xdata(xdata)
        self.lines.set_ydata(ydata)

        #self.text.set_text(str(xdata) + ' K')
        print(xdata[i])
        print(ydata[i])
        print('---------------x                  y------------------------')
        text = self.ax.text(xdata[i],ydata[i], '', ha='right', va='top', fontsize=6)
        text.set_text(val)
        text.set_color(color)
        #self.text.set_color(colors(i))
        #Need both of these in order to rescale
        #self.ax.relim()
        #self.ax.autoscale_view()
        #We need to draw *and* flush
        self.figure.canvas.draw()
        self.figure.canvas.flush_events()

    #Example
    def run(self,  x , y, size, direction, color):

        #self.on_launch()
        curr_key = str(x) + str(y)
        if curr_key not in  order_flow_dict.keys():
                self.xdata.append(x)
                self.ydata.append(y)

        val = 0
        if direction == 0:
            val = order_flow_dict[str(x) + str(y)][0]
            x = x - size
        else:
            val = order_flow_dict[str(x) + str(y)][1]
            x = x + size

        
        self.on_running(self.xdata, self.ydata, self.i, val , color)
        self.i = self.i + 1
        time.sleep(1)



def update_flow_book(px,ask, ask_vol, bid, bid_vol, trade_vol ,flowbook):
    flowbook.lastPx = px
    flowbook.ask = ask
    flowbook.ask_vol = ask_vol
    flowbook.bid = bid
    flowbook.bid_vol = bid_vol
    flowbook.trade_vol = flowbook.trade_vol + trade_vol


def update_flow(trade_px, trade_vol, side, flowbook):
    left = 0
    right = 0
    if side == 1: # 主买
        left = flowbook.ask_vol
        right = trade_vol - flowbook.ask_vol
    else:
        left = trade_vol - flowbook.bid_vol
        right = flowbook.bid_vol
    return [trade_px, left, right]



def process_market(market, flow_manager, flowbook, plot):

    if ( flow_manager.valid_time(market.time) == False):
        return 

    if flowbook.lastPx == 0:
        flowbook.lastPx = market.lastPx
        flowbook.ask =market.ask1
        flowbook.ask_vol = market.ask_vol1
        flowbook.bid = market.bid1
        flowbook.bid_vol = market.bid_vol1
        flowbook.trade_vol = market.trade_vol
        flowbook.price_up = market.open_price*1.1
        flowbook.price_down = market.open_price*0.9

        return

    px = 0
    left = 0 
    right = 0
    if flowbook.lastPx == market.lastPx:
        #print("curr msg is px equal")
        return 
    if flowbook.lastPx < market.lastPx:  #主买
        px, left, right = update_flow( market.lastPx, market.trade_vol, 1 ,flowbook)
    else:
    
        px, left, right = update_flow( market.lastPx, market.trade_vol, 0, flowbook)
    update_flow_book(market.lastPx, market.ask1, market.ask_vol1, market.bid1, market.bid_vol1, market.trade_vol, flowbook)
    y =  (px - flowbook.price_down ) / (flowbook.price_up - flowbook.price_down) * 100 + 10
    flow_manager.inc()

    curr_key = str(int(flow_manager.x)) + str(int(y))
    if curr_key in order_flow_dict.keys(): #已经有数据了
        curr_list = order_flow_dict[curr_key]
        curr_list[0] = curr_list[0] + int(left)
        curr_list[1] = curr_list[1] + int(right)
        order_flow_dict[curr_key] = curr_list
    else:
        order_flow_dict[curr_key] = [int(left), int(right)]
      

    plot.run(int(flow_manager.x) , int (y), flow_manager.size ,  0 ,'green' )
    plot.run(int(flow_manager.x) , int (y), flow_manager.size ,  1 , 'red' )








#'{"600000": {"name": "浦发银行", "open": 7.27, "close": 7.28, "now": 7.21, "high": 7.27, "low": 7.19, "buy": 7.21, "sell": 7.22, "turnover": 12991819, "volume": 93820911.0, "bid1_volume": 23200, "bid1": 7.21, "bid2_volume": 733994, "bid2": 7.2, "bid3_volume": 771200, "bid3": 7.19, "bid4_volume": 500400, "bid4": 7.18, "bid5_volume": 223000, "bid5": 7.17, "ask1_volume": 271010, "ask1": 7.22, "ask2_volume": 658214, "ask2": 7.23, 
#"ask3_volume": 261600, "ask3": 7.24, "ask4_volume": 193500, "ask4": 7.25, "ask5_volume": 111400, "ask5": 7.26, "date": "2022-08-18", "time": "15:00:00"}}'
def recv_market():
    quotation = easyquotation.use('sina')
    flow_manager = FlowManager()
    flow_book = FlowBook()
    d = DynamicUpdate()
    #d.on_launch()
    init_trade_pre = 0
    while(True):
        market = str(quotation.real('sh603260')) # 新浪 ['sina'] 腾讯 ['tencent', 'qq'] 
        #print(market)
        market = market.replace("'", '"')
        market_json = json.loads(market)
        
        msg = Market()
        msg.lastPx     =  market_json["603260"]["now"]
        msg.ask1       =  market_json["603260"]["ask1"]
        msg.bid1       =  market_json["603260"]["bid1"]
        msg.ask_vol1   =  market_json["603260"]["ask1_volume"]
        msg.bid_vol1   =  market_json["603260"]["bid1_volume"]
        if init_trade_pre ==0:
            msg.trade_vol = 0
            init_trade_pre = market_json["603260"]["turnover"]
        else:
            msg.trade_vol  =  market_json["603260"]["turnover"] - init_trade_pre
            init_trade_pre = market_json["603260"]["turnover"]
        msg.open_price =  market_json["603260"]["open"]
        
        datetime_str = market_json["603260"]["date"]+" "+ market_json["603260"]["time"]
        datetime_object = dt.datetime.strptime(datetime_str, '%Y-%m-%d %H:%M:%S')
        msg.time       =  datetime_object

        process_market(msg, flow_manager, flow_book, d)

        
def recv_market_test():
    quotation = easyquotation.use('sina')
    flow_manager = FlowManager()
    flow_book = FlowBook()
    d = DynamicUpdate()


    while(True):
     
        msg = Market()
        msg.lastPx     = 7.1 #market_json["600000"]["now"]
        msg.ask1       = 7.45   #market_json["600000"]["ask1"]
        msg.bid1       = 7.05  #market_json["600000"]["bid1"]
        msg.ask_vol1   = 500 #market_json["600000"]["ask1_volume"]
        msg.bid_vol1   = 600 #market_json["600000"]["bid1_volume"]
        msg.trade_vol  = 500 #market_json["600000"]["turnover"]
        msg.open_price = 7.25 #market_json["600000"]["open"]
        
        datetime_str =    "2022-08-08 14:23:22" #market_json["600000"]["date"]+" "+ market_json["600000"]["time"]
        datetime_object = dt.datetime.strptime(datetime_str, '%Y-%m-%d %H:%M:%S')
        msg.time       =  datetime_object

        process_market(msg, flow_manager, flow_book, d)



        #1
        msg.lastPx     = 7.45 #market_json["600000"]["now"]
        msg.ask1       = 7.45   #market_json["600000"]["ask1"]
        msg.bid1       = 7.05  #market_json["600000"]["bid1"]
        msg.ask_vol1   = 300 #market_json["600000"]["ask1_volume"]
        msg.bid_vol1   = 600 #market_json["600000"]["bid1_volume"]
        msg.trade_vol  = 700 #market_json["600000"]["turnover"]
        msg.open_price = 7.25 #market_json["600000"]["open"]
        
        datetime_str =    "2022-08-08 14:23:22" #market_json["600000"]["date"]+" "+ market_json["600000"]["time"]
        datetime_object = dt.datetime.strptime(datetime_str, '%Y-%m-%d %H:%M:%S')
        msg.time       =  datetime_object

        process_market(msg, flow_manager, flow_book, d)




        #2

        msg.lastPx     = 7.55 #market_json["600000"]["now"]
        msg.ask1       = 7.55   #market_json["600000"]["ask1"]
        msg.bid1       = 7.45  #market_json["600000"]["bid1"]
        msg.ask_vol1   = 300 #market_json["600000"]["ask1_volume"]
        msg.bid_vol1   = 900 #market_json["600000"]["bid1_volume"]
        msg.trade_vol  = 500 #market_json["600000"]["turnover"]
        msg.open_price = 7.25 #market_json["600000"]["open"]
        
        datetime_str =    "2022-08-08 14:23:22" #market_json["600000"]["date"]+" "+ market_json["600000"]["time"]
        datetime_object = dt.datetime.strptime(datetime_str, '%Y-%m-%d %H:%M:%S')
        msg.time       =  datetime_object

        process_market(msg, flow_manager, flow_book, d)

  
        #3

        msg.lastPx     = 7.56 #market_json["600000"]["now"]
        msg.ask1       = 7.56   #market_json["600000"]["ask1"]
        msg.bid1       = 7.46  #market_json["600000"]["bid1"]
        msg.ask_vol1   = 500 #market_json["600000"]["ask1_volume"]
        msg.bid_vol1   = 600 #market_json["600000"]["bid1_volume"]
        msg.trade_vol  = 400 #market_json["600000"]["turnover"]
        msg.open_price = 7.25 #market_json["600000"]["open"]
        
        datetime_str =    "2022-08-08 14:23:22" #market_json["600000"]["date"]+" "+ market_json["600000"]["time"]
        datetime_object = dt.datetime.strptime(datetime_str, '%Y-%m-%d %H:%M:%S')
        msg.time       =  datetime_object

        process_market(msg, flow_manager, flow_book, d)



        #4

        msg.lastPx     = 7.1 #market_json["600000"]["now"]
        msg.ask1       = 7.45   #market_json["600000"]["ask1"]
        msg.bid1       = 7.05  #market_json["600000"]["bid1"]
        msg.ask_vol1   = 500 #market_json["600000"]["ask1_volume"]
        msg.bid_vol1   = 600 #market_json["600000"]["bid1_volume"]
        msg.trade_vol  = 500 #market_json["600000"]["turnover"]
        msg.open_price = 7.25 #market_json["600000"]["open"]
        
        datetime_str =    "2022-08-08 14:23:22" #market_json["600000"]["date"]+" "+ market_json["600000"]["time"]
        datetime_object = dt.datetime.strptime(datetime_str, '%Y-%m-%d %H:%M:%S')
        msg.time       =  datetime_object

        process_market(msg, flow_manager, flow_book, d)
        time.sleep(100)





















recv_market()
#recv_market_test()










x = list(range(0,100))
y = list(range(0,100))
#plt.plot(x, y, "o", color="black")
plt.xlabel('x')
plt.ylabel('y')
plt.xlim([0, 1000])
plt.ylim([0, 100])
#for i, (x, y) in enumerate(zip(x, y)):
#    plt.text(x, y, i+1, color="red", fontsize=12)
#plt.title('graph!')
#plt.show()



data_list = []

class FlowPoint:
    left = 0
    right = 0
    x = 0
    y = 0
    def __init__(self, x , y , left, right):
        self.left = left
        self.right = right
        self.x = x
    
def replot():
    for item in data_list:
        plt.text(item.x -2, item.y, item.left,color="green", fontsize=5 )
        plt.text(item.x +2, item.y, item.right,color="green", fontsize=5 )
    plt.show

def add_flow(y, left, right,trade_vol):

    data.append(FlowPoint(20, y, left, right ))
    plt.cla()
    replot()

    #plt.text(20 - 2, y,left ,color="green", fontsize=5)
    #plt.text(20 + 2, y,right ,color="red", fontsize=5)
    #plt.show()
    #plt.draw()



for i in range(10,20):
    time.sleep(2)
    add_flow(i+ 5 , 30 ,40 , 300)
    plt.draw()
#plt.show()